<?php
require_once('include/My/DbHelper.php');
require_once('include/My/Email.php');
require_once('include/My/Alert.php');

Class Activity
{
    protected $newRecord = false;
    public $db;
    /**
     *
     * 86400 = onwership calculate in days
     * 3600 = onwership calculate in hours
     * 60 = onwership calculate in minutes
     * 1 = onwership calculate in secons
     */
    const TIME_DURATION = 60;
    protected $roles;
    protected $time;
    protected $debug = false;
    
    public function __construct()
    {
        global $sugar_config;
        
        $this->db      = DbHelper::getDb();
        $this->time    = $sugar_config['leadbullet']['interval'] * self::TIME_DURATION;
        $this->roles = $sugar_config['leadbullet']['stages_roles'];
    }
    
    public function setRecordFlag($flag = true)
    {
        $this->newRecord = $flag;
    }
    
    public function manage($focus)
    {
        if ($this->newRecord) {
            $this->add($focus);
        } else if ($focus->deleted) {
            $this->delete($focus);
        }
    }
    
    protected function add($focus) 
    {
        global $current_user, $timedate;
        
        if (!is_array($focus)) {
            $row                = array();
            $row['act_module']  = $focus->module_dir;
            $row['act_bean_id'] = $focus->id;
            $row['module_for']  = $focus->parent_type;
            $row['bean_id_for'] = $focus->parent_id;
            $row['user_id']     = $current_user->id;
            $row['date']        = gmdate($timedate->get_db_date_time_format());
        } else {
            $row = $focus;
        }
        
        DbHelper::insert($row, 'activities');
        DbHelper::update(strtolower($row['module_for']), array('no_activity' => 0), array('id' => $row['bean_id_for']));
    }
    
    protected function delete($focus)
    {
        global $timedate;
        
        $values = array('deleted_at'  => gmdate($timedate->get_db_date_time_format()));
        $where  = array('act_bean_id' => $focus->id);
        
        DbHelper::update('activities', $values, $where);
    }
    
    public function checkActivity($module = 'Accounts', $debug = false, $markInDB = false)
    {
        global $timedate;
        if ($debug) {
            $this->debug = $debug;
        }

        $emailModel = new MyEmail();
        $alertModel = new Alert();
        
        if ($module == 'Accounts') {
            $sql = "SELECT acc.* FROM accounts acc WHERE acc.deleted = 0";
        } else {
            $sql = "SELECT con.*, CONCAT(con.first_name, ' ', con.last_name) as name FROM contacts con WHERE con.deleted = 0";
        }
        
        $beans           = DbHelper::fetchAll($sql);
        $accWithActivity = $this->getAllWithActivity($module);
        $accLastActivity = $this->getLastActivity($module);
        $lastSentAlerts  = $this->getLastAlerts($module);
        $userAlerts      = $this->getAlertsSetByUser($module);
        
        $beanName  = $module == 'Accounts'? 'klienta': 'kontaktu';
        $emailMsgs = array(
            1 => "",
            2 => "",
            3 => "",
        );
        $alertsMsg = array(
            1 => array(),
            2 => array(),
            3 => array(),
        );
        
        if ($this->debug) {
            echo '<pre>';
            echo 'Sprawdzenie aktywnosci module = '.$module . '<br>';
            echo 'Ustawiony czas to = '.$this->time . ' sekund ('.($this->time/60).' minut)<br>';
        }
        $allBeansId = array();
        //@todo sprawdzic status klienta
        foreach($beans as $bean) {
            //przyjmujemy że jest aktywnosc
            $activityFlag = true; 
            if ($this->debug) {
                echo '<br><br><br>Sprawdzenie dla: '.$bean['id'].' ('.$bean['name'].') <br>';
            }
            
            //the code
            //istnieje aktywnosc w zdefioniwanym przedziale czasu - nic nie robimy
            if (in_array($bean['id'], $accWithActivity)) {
                if ($this->debug) {
                    echo 'Dla ' .$bean['id'] . ' Istnieje aktywnosc w zdefiniwoanym przedziale czasu'. '<br>';
                }
                continue;
            }
            
            //jezeli uzytkownik ustawil sobie powiadomienie - nie wysyalmy jeszcze raz
            if (isset($userAlerts[$bean['id']])) {
                if ($this->debug) {
                    echo 'Dla ' .$bean['id'] . ' zostało ustawione powiadomienie'. '<br>';
                }
                continue;
            }
            
            // czy od ostatniej aktywnosci zostalo wyslane powiadomienie - jezeli tak - nie wysyalmy
            $dateNow     = new DateTime(gmdate("Y-m-d H:i:s"));
            
            if (isset($accLastActivity[$bean['id']])) {
                $lastActDate = new DateTime($accLastActivity[$bean['id']]);
                if ($this->debug) {
                    echo 'Dla ' .$bean['id'] . ' Istnieje aktywnosc w zdefiniwoanym przedziale czasu'. $accLastActivity[$bean['id']] .'<br>';
                }
                
                if (isset($lastSentAlerts[$bean['id']])) {
                    if ($this->debug) {
                        echo 'Dla ' .$bean['id'] . ' Istnieje wyslany alert:'.$lastSentAlerts[$bean['id']] .'<br>';
                    }
                    //istnieje aktywnosc i wyslany alert
                    $lastAlertDate = new DateTime($lastSentAlerts[$bean['id']]);
                    
                    if ($lastAlertDate > $lastActDate) {//alert zostal wysalny po aktywnosci - koniec
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' alert zostal wysalny po aktywnosci - koniec'. '<br>';
                        }
                        continue;
                    } else {//alert zostal wysalny przed aktywnoscia - sprawdzic czy od 'teraz' minal czas
                        $diff = $dateNow->getTimestamp() - $lastActDate->getTimestamp();
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' alert zostal wysalny przed aktywnoscia'. '<br>';
                        }
                        if ($diff > $this->time) {
                            $activityFlag = false;
                            if ($this->debug) {
                                echo 'Dla ' .$bean['id'] . ' alert zostal wysalny przed aktywnoscia i minal czas - wysylamy powiadomienie'. '<br>';
                            }
                        } else {
                            if ($this->debug) {
                                echo 'Dla ' .$bean['id'] . ' alert zostal wysalny przed aktywnoscia i NIE minal czas - NIE wysylamy powiadomienie'. '<br>';
                            }
                        }
                    }
                } else {
                    //jest aktywnosc, nie ma alertu - sprawdzic czy minal zdefiniwany czas
                    if ($this->debug) {
                        echo 'Dla ' .$bean['id'] . ' jest aktywnosc, nie ma alertu - sprawdzic czy minal zdefiniwany czas'. '<br>';
                    }
                    $diff = $dateNow->getTimestamp() - $lastActDate->getTimestamp();
                    if ($diff > $this->time) {
                        $activityFlag = false;
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' jest aktywnosc, nie ma alertu - minal czas - wysyalmy powiadomienie'. '<br>';
                        }
                    } else {
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' jest aktywnosc, nie ma alertu - NIE minal czas - nie wysyalmy jeszcze powiadomienia'. '<br>';
                        }
                    }
                }
            } else {
                //nie istnieje zadna aktywnosc dla tego bean - 
                if ($this->debug) {
                    echo 'Dla ' .$bean['id'] . ' nie istnieje zadna aktywnosc dla tego bean czasu utworzenia '. $bean['date_entered'].'<br>';
                }
                $dateEntered = new DateTime($bean['date_entered']);
                //sprawdzic czy zostal wysalny alert
                if (isset($lastSentAlerts[$bean['id']])) {
                    if ($this->debug) {
                        echo 'Dla ' .$bean['id'] . ' Istnieje wyslany alert:'.$lastSentAlerts[$bean['id']] .'<br>';
                    }
                    $lastAlertDate = new DateTime($lastSentAlerts[$bean['id']]);
                    if ($dateEntered > $lastAlertDate) {
                        $activityFlag = false;
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' od utworzenia bean nie zostalo wyslane powiadomienie - wysylamy'. '<br>';
                        }
                    } else {
                        if ($this->debug) {
                            echo 'Dla ' .$bean['id'] . ' od utworzenia bean zostalo wyslane powiadomienie - koniec'. '<br>';
                        }
                    }
                    continue;
                }
                //sprawdzic czy od daty utworzenia minal zdefiniowany czas, jezeli tak wyslac alert
                $diff        = $dateNow->getTimestamp() - $dateEntered->getTimestamp();
                if ($diff > $this->time) {
                    $activityFlag = false;
                    if ($this->debug) {
                        echo 'Dla ' .$bean['id'] . ' od utworzenia bean minal czas - wysyalmy powiadomienie'. '<br>';
                    }
                } else {
                    if ($this->debug) {
                        echo 'Dla ' .$bean['id'] . ' od utworzenia bean NIE minal czas - nie wysyalmy jeszcze powiadomienie'. '<br>';
                    }
                }
            }
            
            if (!$activityFlag) {
                $alert    = array(
                    'bean_id' => $bean['id'], 
                    'module'  => $module, 
                    'date'    => gmdate($timedate->get_db_date_time_format()),
                    'sent'    => 1,
                    'type'    => 'robot'
                );
                
                $stage = (int)$bean['stage'];
                if (is_null($bean['stage'])) {
                    $stage = 1;
                }
                
                $emailMsgs[$stage]  .= "Brak aktywności dla $beanName: '". $bean['name'] . "'<br>";
                $alertsMsg[$stage][] = $alert;
                $allBeansId[] = $bean['id'];
            }
            
        }
        if ($this->debug) {
            print_r($alertsMsg);
            print_r($emailMsgs);
        }

        if ($markInDB) {
            if (empty($allBeansId)) {
                return true;
            }
            $sql = "UPDATE " .strtolower($module) . " SET no_activity = '1' WHERE " .
                   "id IN ('" . implode("','", $allBeansId) . "')";
            DbHelper::getDb()->query($sql);
            return true;
        }
        
        foreach ($alertsMsg as $stage => $arts) {
            if (!empty($arts)) {
                
                $emailUsers = $this->getEmailUsers($this->roles[$stage]);
                $emailModel->send(array_values($emailUsers), 'CRM - Brak aktywności', $emailMsgs[$stage]);
                $alertModel->insertAll($alertsMsg[$stage]);
            }
        }
        
        return true;
    }
    
    protected function getAllWithActivity($module = 'Accounts')
    {
        $sql = "SELECT DISTINCT bean_id_for FROM activities WHERE module_for = '$module'
            AND deleted_at IS NULL
            AND UNIX_TIMESTAMP() - UNIX_TIMESTAMP(date) <= '$this->time'";
        
        $data = DbHelper::fetchAll($sql, 'bean_id_for');
        
        return $data;
    }
    
    protected function getLastActivity($module = 'Accounts')
    {
        $sql = "SELECT bean_id_for, max(date) as date FROM activities
                WHERE deleted_at IS NULL AND module_for = '$module'
                group by bean_id_for";
        
        $data = DbHelper::fetchPairs($sql, 'bean_id_for', 'date');

        return $data;
    }
    
    protected function getLastAlerts($module = 'Accounts')
    {
        $sql = "SELECT bean_id, max(date) as date FROM alerts
                WHERE  module = '$module' AND sent = 1
                group by bean_id";
        
        $data = DbHelper::fetchPairs($sql, 'bean_id', 'date');

        return $data;
    }
    
    protected function getAlertsSetByUser($module = 'Accounts')
    {
        $sql = "SELECT bean_id, max(date) as date FROM alerts
                WHERE  module = '$module' AND sent = 0 AND type = 'user'
                AND UNIX_TIMESTAMP(CURDATE()) <= UNIX_TIMESTAMP(date)
                group by bean_id";

        $data = DbHelper::fetchPairs($sql, 'bean_id', 'date');

        return $data;
    }
    
    public function getEmailUsers($roleId)
    {
        $sql = "SELECT u.id as user_id, ea.email_address as email FROM acl_roles_users aru
                INNER JOIN users u ON u.id = aru.user_id
                INNER JOIN email_addr_bean_rel eabr ON eabr.bean_id = u.id AND bean_module = 'Users' AND eabr.primary_address = 1
                INNER JOIN email_addresses ea ON eabr.email_address_id = ea.id
                WHERE role_id = '". $roleId ."' and aru.deleted = 0
                AND u.deleted = 0 AND u.status = 'Active' AND ea.deleted = 0";

        $data = DbHelper::fetchPairs($sql, 'user_id', 'email');
        
        return $data;
    }
    
    

    
}
